import { getProjectCssPath } from "../render";
// import { folderTreeType } from "../server";
import * as prettier from "prettier";
import {
  analyserResult,
  fileObjType,
  getRequestFileName,
} from "./htmlAnalyser";

const path = require("path");
const fs = require("fs");

export const resolveUrl = (
  fileObj: fileObjType,
  prefix: { css: string; img: string }
) => {
  //, prefix: string
  const reg = new RegExp(/url\([\s\S]*?\)/gi);
  const arr = fileObj.file.match(reg);
  if (arr === null) return [];
  return arr.map((url) => {
    let requestPath = url.substring(4, url.length - 1).trim();
    if (requestPath.indexOf("/*") > -1)
      requestPath = removeCssComment(requestPath);

    if (requestPath.startsWith('"')) {
      requestPath = requestPath.substring(1, requestPath.lastIndexOf('"'));
    } else if (requestPath.startsWith("'")) {
      requestPath = requestPath.substring(1, requestPath.lastIndexOf("'"));
    }
    // if (requestPath.startsWith('"') || requestPath.startsWith("'"))
    //   requestPath = requestPath.substring(1, requestPath.length - 1);
    let requestFileName = path.basename(
      getRequestFileName(
        requestPath,
        fileObj,
        fileObj.folderTree,
        (requestFileName) => requestFileName
      )
    );
    //console.log(requestPath, requestFileName);

    return {
      origin: url,
      replaceWith: `url("${
        path.extname(requestFileName) === ".css" ? prefix.css : prefix.img
      }/${requestFileName}")`,
    };
  });
};
// const resolveCssBackground = (fileObj: fileObjType) => {
//   const backgroundReg = new RegExp(
//     /background(.|\n){0,20}?url(.|\n){0,50}?;/gi
//   );
//   const arr = fileObj.file.match(backgroundReg);

//   if (arr === null) return [];

//   return arr
//     .map((val) => {
//       const matched = val.match(/url\((.|\n)*?\)/gi);
//       if (!matched) {
//         console.error(val);

//         return {
//           origin: "",
//           replaceWith: "",
//         };
//       }
//       const url = matched[0];
//       // let stripUrl = url.substring(4, url.length - 1).trim(); //remove redundant text wrap
//       let requestPath = url.substring(4, url.length - 1).trim();
//       if (requestPath.startsWith('"') || requestPath.startsWith("'"))
//         requestPath = requestPath.substring(1, requestPath.length - 1);
//       let requestFileName = path.basename(
//         getRequestFileName(
//           requestPath,
//           fileObj,
//           fileObj.folderTree,
//           (requestFileName) => requestFileName
//         )
//       );
//       //remove quote

//       // const last = stripUrl.lastIndexOf("/");
//       // if (last != -1) stripUrl = stripUrl.substring(last + 1);
//       return {
//         origin: url,
//         replaceWith: `url("../img/${requestFileName}")`,
//       };
//     })
//     .filter((val) => val.origin !== "");
// };

export const cssRelink = (fileObj: fileObjType): analyserResult[] => {
  // match all background
  // const backgroundReplacer = resolveCssBackground(fileObj);
  const urlReplacer = resolveUrl(fileObj, {
    css: "../css",
    img: "../img",
  });
  // console.log(backgroundReplacer, "backgroundReplacer", fileObj.filePath);

  return urlReplacer;
};
export const prettyCss = async (file: string): Promise<string> => {
  return await prettier.format(file, { semi: false, parser: "css" });
};
export const removeCssComment = (file: string): string => {
  return file.replace(/\/\*[\s\S]*?\*\//g, "");
};
export const cleanCssLinks = async (
  file: string,
  index: number
): Promise<string> => {
  const reg = /background(.|\r|\n)*?;/gi;
  let css = await prettyCss(file);
  const arr = css.match(reg) || [];
  arr.forEach((val: any) => {
    if (val.indexOf("http") > -1 || val.indexOf("urn:") > -1) {
      if (val.length > 150 && val.indexOf("{") > -1) {
        console.log("error:", val);
        return;
      }
      css = css.replace(val, "");
    }
  });
  return css;
};

export const addCssFileAndQuote = (
  content: string,
  indexFile: string,
  fileName: string
): string => {
  if (!fileName.endsWith(".css")) {
    fileName = fileName += ".css";
  }
  const cssPath = path.resolve(getProjectCssPath(), fileName);
  fs.writeFileSync(cssPath, content);
  let quote = `<link rel="stylesheet" type="text/css" href="res/css/${fileName}" />`;
  if (indexFile.indexOf(quote) > -1) return indexFile;
  return indexFile.replace("</head>", `\n\t${quote}\n</head>`);
};

/**
 * @param tag
 * @returns src and file name from tag
 */
export const stripSrc = (tag: string): { src: string; name: string } => {
  const reg = /src=("|').*("|')/i;
  const res = tag.match(reg);
  if (!res) return { src: "", name: "" };
  const src = res[0].substring(5, res[0].length - 1);
  return {
    src,
    name: src.substring(src.lastIndexOf("/") + 1),
  };
};

export const stripHref = (tag: string): { src: string; name: string } => {
  const reg = /href=("|').*?("|')/i;
  const res = tag.match(reg);
  if (!res) return { src: "", name: "" };
  const src = res[0].substring(6, res[0].length - 1);
  return {
    src,
    name: src.substring(src.lastIndexOf("/") + 1),
  };
};

export const scopeCssFile = (file: string, mark: string): string => {
  let res = "";
  const reg = /[a-zA-Z\.#]/;
  mark = ` #${mark} `;
  let status = [];
  let comment = false,
    start = false,
    meta = false,
    string = false;
  let stringFlag = "";
  for (let i = 0; i < file.length; i++) {
    const element = file[i];

    if (!string) {
      // console.log(element, "---", status);

      if (element === "/") {
        if (status.length > 0 && status[status.length - 1] === "*") {
          status = [];
          comment = false;
        } else status.push("/");
        continue;
      }
      if (element === "*") {
        if (status.length > 0 && status[status.length - 1] === "/") {
          status = [];
          comment = true;
        } else status.push("*");
        continue;
      }
    }

    if (comment) continue;

    if (element === "@") meta = true;
    if (meta && element === ";") meta = false;

    if (element === '"' || element == "'") {
      if (stringFlag === element) {
        stringFlag = "";
        string = false;
        // console.log(stringFlag, file[i - 1]);
      } else {
        stringFlag = element;
        string = true;
      }
    }

    if (status.length > 0 && status[status.length - 1] === "*") {
      res += "*";
      status = [];
    }
    if (element === "{") start = true;
    else if (element === "}") start = false;
    if (start === false && !comment && !meta && reg.test(element)) {
      res += mark;
      start = true;
    }
    res += element;
    if (element === ",") {
      res += mark;
    }
  }
  return res;
};

/**
 *
 * @param content css file content
 * @returns generated css file path
 */
export const genCssFile = (content: string): string => {
  let seq = 0;
  const cssPath = getProjectCssPath();
  while (fs.existsSync(path.resolve(cssPath, seq + "unique.css"))) seq++;
  const destPath = path.resolve(cssPath, seq + "unique.css");
  fs.writeFileSync(destPath, content);
  return seq + "unique.css";
};
